#!/usr/bin/python
# -*- coding: utf-8 -*-

from __future__ import division
import wx

class LowDrawer:
    def __init__(self, dc):
        self.dc = dc
        FONT_SIZE = 10
        self.dc.SetFont(wx.Font(FONT_SIZE, wx.SWISS, wx.NORMAL, wx.NORMAL))

    def draw_main_rect(self, rect):
        self.dc.SetBackground(wx.Brush(wx.WHITE))
        self.dc.Clear()
        self.dc.DrawRectangleRect(rect)

    def draw_lines(self, dots, color):
        LINE_PEN_WIDTH = 2
        self.dc.SetPen(wx.Pen(color, LINE_PEN_WIDTH))
        self.dc.DrawLines(dots)
        self.dc.SetPen(wx.NullPen)

    def draw_axis_text(self, text, x, y, orient):
        tw, th = self.dc.GetTextExtent(text)
        if orient == 'x':
            x -= tw // 2
        elif orient == 'y':
            x, y = x - tw, y - (th // 2)
        self.dc.DrawText(text, x, y)

    def draw_axis_line(self, x1, y1, x2, y2):
        NET_PEN_WIDTH = 1
        self.dc.SetPen(wx.Pen(wx.GREEN, NET_PEN_WIDTH, wx.DOT))
        self.dc.DrawLine(x1, y1, x2, y2)
        self.dc.SetPen(wx.NullPen)

    def draw_text(self, x, y, text, color):
        self.dc.SetTextForeground(color)
        self.dc.DrawText(text, x, y)
        self.dc.SetTextForeground(wx.BLACK)

    def set_clipping(self, rect):
        self.dc.SetClippingRect(rect)

    def destroy_clipping(self):
        self.dc.DestroyClippingRegion()

    def get_size_tuple(self):
        return self.dc.GetSizeTuple()

class EmptyLowDrawer(): # Maybe it is not good decision
    def __init__(self, dc = None): pass
    def get_size_tuple(self):
        return (0, 0)

class Drawer:
    def __init__(self, sampleSettings):
        self.sampleSettings, self.additionOffsets = sampleSettings, (0, 0)
        self.lowDrawer = EmptyLowDrawer()

    def update_dc(self, dc):
        self.lowDrawer = LowDrawer(dc)
        self.calc_dimensions(self.sampleSettings, self.additionOffsets)
        self.lowDrawer.draw_main_rect(self.rect)

    def update_settings(self, sampleSettings):
        self.sampleSettings = sampleSettings
        self.calc_dimensions(self.sampleSettings, self.additionOffsets)

    def calc_dimensions(self, sampleSettings, additionOffsets):
        mainOffset = 40
        width, height = self.lowDrawer.get_size_tuple()

        if not additionOffsets: additionOffsets = (0, 0)
        downOffset, rightOffset = additionOffsets[0] * 15, additionOffsets[1] * 100
        self.rect = [self.rectLeft, self.rectUp, self.rectWidth, self.rectHeight] = [
                    mainOffset, mainOffset, width - mainOffset * 2 - rightOffset,
                     height - mainOffset * 2 - downOffset]
        try:
            self.kyStoP = self.rectHeight / (sampleSettings.ySampleMax - sampleSettings.ySampleMin)
            self.kxStoP = self.rectWidth / (sampleSettings.xSampleWidth)
        except ZeroDivisionError:
            self.kyStoP, self.kxStoP = 1.0, 1.0
        self.yPix0 = self.rectUp + self.kyStoP*sampleSettings.ySampleMax
        self.xFin = self.rectLeft + self.rectWidth

    def set_clipping(self):
        self.lowDrawer.set_clipping(self.rect)

    def destroy_clipping(self):
        self.lowDrawer.destroy_clipping()

    def draw_step_line(self, line, color):
        dots = [(self.xFin -  self.kxStoP*i, self.yPix0 - y*self.kyStoP) for i, y in enumerate(reversed(line))]
        self.lowDrawer.draw_lines(dots, color)

    def draw_x_axis_text(self, text, x):
        yForXAxis = self.rectUp + self.rectHeight + 5
        self.lowDrawer.draw_axis_text(text, self.xFin - self.kxStoP*x, yForXAxis, 'x')

    def draw_y_axis_text(self, text, y):
        xForXAxis = self.rectLeft - 5
        self.lowDrawer.draw_axis_text(text, xForXAxis, self.yPix0 - self.kyStoP*y, 'y')

    def draw_x_axis_net(self, x):
        xPix = self.xFin - self.kxStoP*x
        self.lowDrawer.draw_axis_line(xPix, self.rectUp, xPix, self.rectUp + self.rectHeight)

    def draw_y_axis_net(self, y):
        yReal = self.yPix0 - y * self.kyStoP
        self.lowDrawer.draw_axis_line(self.rectLeft, yReal, self.rectLeft + self.rectWidth, yReal)

    def draw_down_legend(self, n, text, color):
        self.lowDrawer.draw_text(40, self.rectUp + self.rectHeight + 30 + n * 15, text, color)


if __name__ == "__main__":
    execfile("test_drawer.py")
